package log

import (
	"fmt"
	"os"
)

var DefaultMessageKey = "msg"

type Option func(*logcat)

var LogCat *logcat

type logcat struct {
	logger  Logger
	msgKey  string
	sprint  func(...interface{}) string
	sprintf func(format string, a ...interface{}) string
}

// 创建日志结构体
func NewLogger(l Logger, opts ...Option) *logcat {
	log := &logcat{
		logger:  l,
		msgKey:  DefaultMessageKey,
		sprint:  fmt.Sprint,
		sprintf: fmt.Sprintf,
	}
	for _, o := range opts {
		o(log)
	}
	return log
}

// 设置默认messageKey
func WithMessageKey(k string) Option {
	return func(opts *logcat) {
		opts.msgKey = k
	}
}

func (l *logcat) Log(level Level, keyvals ...interface{}) {
	l.logger.Log(level, keyvals...)
}

// Debug logs a message at debug level.
func (l *logcat) Debug(a ...interface{}) {
	l.logger.Log(LevelDebug, l.msgKey, l.sprint(a...))
}

// Debugf logs a message at debug level.
func (l *logcat) Debugf(format string, a ...interface{}) {
	l.logger.Log(LevelDebug, l.msgKey, l.sprintf(format, a...))
}

// Debugw logs a message at debug level.
func (l *logcat) Debugw(keyvals ...interface{}) {
	l.logger.Log(LevelDebug, keyvals...)
}

// Info logs a message at info level.
func (l *logcat) Info(a ...interface{}) {
	l.logger.Log(LevelInfo, l.msgKey, l.sprint(a...))
}

// Infof logs a message at info level.
func (l *logcat) Infof(format string, a ...interface{}) {
	l.logger.Log(LevelInfo, l.msgKey, l.sprintf(format, a...))
}

// Infow logs a message at info level.
func (l *logcat) Infow(keyvals ...interface{}) {
	l.logger.Log(LevelInfo, keyvals...)
}

func (l *logcat) Warn(a ...interface{}) {
	l.logger.Log(LevelWarn, l.msgKey, l.sprint(a...))
}

// Warnf logs a message at warnf level.
func (l *logcat) Warnf(format string, a ...interface{}) {
	l.logger.Log(LevelWarn, l.msgKey, l.sprintf(format, a...))
}

// Warnw logs a message at warnf level.
func (l *logcat) Warnw(keyvals ...interface{}) {
	l.logger.Log(LevelWarn, keyvals...)
}

// Error logs a message at error level.
func (l *logcat) Error(a ...interface{}) {
	_ = l.logger.Log(LevelError, l.msgKey, l.sprint(a...))
}

// Errorf logs a message at error level.
func (l *logcat) Errorf(format string, a ...interface{}) {
	_ = l.logger.Log(LevelError, l.msgKey, l.sprintf(format, a...))
}

// Errorw logs a message at error level.
func (l *logcat) Errorw(keyvals ...interface{}) {
	_ = l.logger.Log(LevelError, keyvals...)
}

// Fatal logs a message at fatal level.
func (l *logcat) Fatal(a ...interface{}) {
	l.logger.Log(LevelFatal, l.msgKey, l.sprint(a...))
	os.Exit(1)
}

// Fatalf logs a message at fatal level.
func (l *logcat) Fatalf(format string, a ...interface{}) {
	l.logger.Log(LevelFatal, l.msgKey, l.sprintf(format, a...))
	os.Exit(1)
}

// Fatalw logs a message at fatal level.
func (l *logcat) Fatalw(keyvals ...interface{}) {
	_ = l.logger.Log(LevelFatal, keyvals...)
	os.Exit(1)
}
